/*
 * @brief: 
 * @Author: TzzzT
 * @Date: 2022-05-08 21:37:01
 * @LastEditTime: 2022-11-29 03:11:38
 * @LastEditors: TzzzT
 */

#include "freertos/FreeRTOS.h"
#include "freertos/task.h"
#include "freertos/queue.h"
#include "driver/gpio.h"
#include "esp_log.h"
#include "spi.h"
#include "mfrc522.h"

#include "RCS_nfc.h"
#include "RCS_slave.h"
#include "RCS_protocol.h"

static const char *NFC_TAG = "NFC_TAG";

extern QueueHandle_t xUploadDataQueue;
extern rcs_slave_system_t rcsSystem;

esp_err_t nfc_init(void){
    //先初始化spi引脚
    esp_err_t ret = ESP_FAIL;
    ret = spi_init(PIN_NUM_CLK, PIN_NUM_MOSI, PIN_NUM_MISO);
    if(ret != ESP_OK){
        return ret;
    }

    //配置寄存器，开启天线
    MFRC522_Pin_Init(PIN_NUM_RST, PIN_NUM_CS);
    ret = MFRC522_Start();
    return ret;
}

void open_rc522(void){
    MFRC522_Start();
}

static void analyse_tag_command(uint8_t* block){
    if(block[1] != 0){
        block[1]--;
        uint8_t prop = block[0];
        uint8_t command = 0;
        switch (prop){
        case NFC_INCREASE_DAMAGE:
            command = INCREASE_DAMAGE_COMM;
            break;
        case NFC_INCREASE_HP:
            command = INCREASE_HP_COMM;
            break;
        case NFC_REBORN:
            command = REBORN_COMM;
            break;
        case NFC_INCREASE_BULLET_NUM:
            command = INCREASE_BULLET_COMM;
            break;        
        default:
            break;
        }
        uint8_t pack_len = 0;
        uint8_t* package = make_command_package(command, &pack_len);
        ESP_LOGI(NFC_TAG,"put nfc_command_package in queue");
        if (xQueueSend(xUploadDataQueue, package, pdMS_TO_TICKS(200)) != pdPASS) {
            ESP_LOGE(NFC_TAG,"queue full.");
        }
        free(package);
    }
}



#define BLOCK_NUM 8
void detect_tag(void){
    uint8_t ret = 0xff;
    uint8_t tag_type[2] = {0};
    uint8_t tag_seri[4] = {0};
    uint8_t key[6] = {0xff,0xff,0xff,0xff,0xff,0xff};
    uint8_t block_data[16] = {0};
    char strprt[50] = {0};
    ret = MFRC522_Request(PICC_REQIDL, tag_type);
    if(ret != MI_OK){
        return;
    }
    ESP_LOGI(NFC_TAG, "get Tag type:%02x%02x.", tag_type[0], tag_type[1]);
    if(MFRC522_Anticoll(tag_seri) != MI_OK){
        return;
    }
    sprintf ( strprt, "The Card ID is: %02X%02X%02X%02X", tag_seri[0], tag_seri[1], tag_seri[2], tag_seri[3]);				
    printf ("%s\r\n",strprt); 
    ret = MFRC522_SelectTag(tag_seri);
    ESP_LOGI(NFC_TAG, "SelectTag size:%d", ret);
    ret = MFRC522_Auth(PICC_AUTHENT1A, BLOCK_NUM, key, tag_seri);//选择扇区
    ret = MFRC522_Read(BLOCK_NUM, block_data);
    if(ret != MI_OK){
        ESP_LOGE(NFC_TAG, "read error");
        return;
    }
    ESP_LOGI(NFC_TAG, "read success:%02x %02x", block_data[0], block_data[1]);
    analyse_tag_command(block_data);

    ret = MFRC522_Write(BLOCK_NUM, block_data);
    if(ret != MI_OK){
        ESP_LOGE(NFC_TAG, "write error");
        return;
    }
    ESP_LOGI(NFC_TAG, "write success:%02x %02x", block_data[0], block_data[1]);
}


void close_rc522(void){
    MFRC522_Reset();
}


void test_add_increase_damage_tag(void){
    uint8_t ret = 0xff;
    uint8_t tag_type[2] = {0};
    uint8_t tag_seri[4] = {0};
    uint8_t key[6] = {0xff,0xff,0xff,0xff,0xff,0xff};
    uint8_t block_data[16] = {0};
    char strprt[50] = {0};
    ret = MFRC522_Request(PICC_REQIDL, tag_type);
    if(ret != MI_OK){
        return;
        //ret = MFRC522_Request(PICC_REQALL, tag_id);
    }
    ESP_LOGI(NFC_TAG, "get Tag type:%02x%02x.", tag_type[0], tag_type[1]);
    if(MFRC522_Anticoll(tag_seri) != MI_OK){
        return;
    }
    sprintf ( strprt, "The Card ID is: %02X%02X%02X%02X", tag_seri[0], tag_seri[1], tag_seri[2], tag_seri[3]);				
    printf ("%s\r\n",strprt); 
    ret = MFRC522_SelectTag(tag_seri);
    ESP_LOGI(NFC_TAG, "SelectTag size:%d", ret);
    ret = MFRC522_Auth(PICC_AUTHENT1A, BLOCK_NUM, key, tag_seri);//选择扇区
    ret = MFRC522_Read(BLOCK_NUM, block_data);
    if(ret != MI_OK){
        ESP_LOGE(NFC_TAG, "read error");
        return;
    }
    ESP_LOGI(NFC_TAG, "read success:%02x %02x", block_data[0], block_data[1]);
    block_data[0] = 0;
    block_data[1] += 10;
    ret = MFRC522_Write(BLOCK_NUM, block_data);
    if(ret != MI_OK){
        ESP_LOGE(NFC_TAG, "write error");
        return;
    }
    ESP_LOGI(NFC_TAG, "write success:%02x %02x", block_data[0], block_data[1]);
}

void test_add_increase_hp_tag(void){
    uint8_t ret = 0xff;
    uint8_t tag_type[2] = {0};
    uint8_t tag_seri[4] = {0};
    uint8_t key[6] = {0xff,0xff,0xff,0xff,0xff,0xff};
    uint8_t block_data[16] = {0};
    char strprt[50] = {0};
    ret = MFRC522_Request(PICC_REQIDL, tag_type);
    if(ret != MI_OK){
        return;
        //ret = MFRC522_Request(PICC_REQALL, tag_id);
    }
    ESP_LOGI(NFC_TAG, "get Tag type:%02x%02x.", tag_type[0], tag_type[1]);
    if(MFRC522_Anticoll(tag_seri) != MI_OK){
        return;
    }
    sprintf ( strprt, "The Card ID is: %02X%02X%02X%02X", tag_seri[0], tag_seri[1], tag_seri[2], tag_seri[3]);				
    printf ("%s\r\n",strprt); 
    ret = MFRC522_SelectTag(tag_seri);
    ESP_LOGI(NFC_TAG, "SelectTag size:%d", ret);
    ret = MFRC522_Auth(PICC_AUTHENT1A, BLOCK_NUM, key, tag_seri);//选择扇区
    ret = MFRC522_Read(BLOCK_NUM, block_data);
    if(ret != MI_OK){
        ESP_LOGE(NFC_TAG, "read error");
        return;
    }
    ESP_LOGI(NFC_TAG, "read success:%02x %02x", block_data[0], block_data[1]);
    block_data[0] = 1;
    block_data[1] += 10;
    ret = MFRC522_Write(BLOCK_NUM, block_data);
    if(ret != MI_OK){
        ESP_LOGE(NFC_TAG, "write error");
        return;
    }
    ESP_LOGI(NFC_TAG, "write success:%02x %02x", block_data[0], block_data[1]);
}

void test_add_reborn_tag(void){
    uint8_t ret = 0xff;
    uint8_t tag_type[2] = {0};
    uint8_t tag_seri[4] = {0};
    uint8_t key[6] = {0xff,0xff,0xff,0xff,0xff,0xff};
    uint8_t block_data[16] = {0};
    char strprt[50] = {0};
    ret = MFRC522_Request(PICC_REQIDL, tag_type);
    if(ret != MI_OK){
        return;
        //ret = MFRC522_Request(PICC_REQALL, tag_id);
    }
    ESP_LOGI(NFC_TAG, "get Tag type:%02x%02x.", tag_type[0], tag_type[1]);
    if(MFRC522_Anticoll(tag_seri) != MI_OK){
        return;
    }
    sprintf ( strprt, "The Card ID is: %02X%02X%02X%02X", tag_seri[0], tag_seri[1], tag_seri[2], tag_seri[3]);				
    printf ("%s\r\n",strprt); 
    ret = MFRC522_SelectTag(tag_seri);
    ESP_LOGI(NFC_TAG, "SelectTag size:%d", ret);
    ret = MFRC522_Auth(PICC_AUTHENT1A, BLOCK_NUM, key, tag_seri);//选择扇区
    ret = MFRC522_Read(BLOCK_NUM, block_data);
    if(ret != MI_OK){
        ESP_LOGE(NFC_TAG, "read error");
        return;
    }
    ESP_LOGI(NFC_TAG, "read success:%02x %02x", block_data[0], block_data[1]);
    block_data[0] = 2;
    block_data[1] += 10;
    ret = MFRC522_Write(BLOCK_NUM, block_data);
    if(ret != MI_OK){
        ESP_LOGE(NFC_TAG, "write error");
        return;
    }
    ESP_LOGI(NFC_TAG, "write success:%02x %02x", block_data[0], block_data[1]);
}

void test_add_increase_bulletnum_tag(void){
    uint8_t ret = 0xff;
    uint8_t tag_type[2] = {0};
    uint8_t tag_seri[4] = {0};
    uint8_t key[6] = {0xff,0xff,0xff,0xff,0xff,0xff};
    uint8_t block_data[16] = {0};
    char strprt[50] = {0};
    ret = MFRC522_Request(PICC_REQIDL, tag_type);
    if(ret != MI_OK){
        return;
        //ret = MFRC522_Request(PICC_REQALL, tag_id);
    }
    ESP_LOGI(NFC_TAG, "get Tag type:%02x%02x.", tag_type[0], tag_type[1]);
    if(MFRC522_Anticoll(tag_seri) != MI_OK){
        return;
    }
    sprintf ( strprt, "The Card ID is: %02X%02X%02X%02X", tag_seri[0], tag_seri[1], tag_seri[2], tag_seri[3]);				
    printf ("%s\r\n",strprt); 
    ret = MFRC522_SelectTag(tag_seri);
    ESP_LOGI(NFC_TAG, "SelectTag size:%d", ret);
    ret = MFRC522_Auth(PICC_AUTHENT1A, BLOCK_NUM, key, tag_seri);//选择扇区
    ret = MFRC522_Read(BLOCK_NUM, block_data);
    if(ret != MI_OK){
        ESP_LOGE(NFC_TAG, "read error");
        return;
    }
    ESP_LOGI(NFC_TAG, "read success:%02x %02x", block_data[0], block_data[1]);
    block_data[0] = 3;
    block_data[1] += 10;
    ret = MFRC522_Write(BLOCK_NUM, block_data);
    if(ret != MI_OK){
        ESP_LOGE(NFC_TAG, "write error");
        return;
    }
    ESP_LOGI(NFC_TAG, "write success:%02x %02x", block_data[0], block_data[1]);
}


